package com.kye.express.business.online_pay;

import android.app.Dialog;
import android.content.Context;
import android.content.Intent;
import android.databinding.DataBindingUtil;
import android.os.Bundle;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;
import android.support.v7.widget.DefaultItemAnimator;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.Toolbar;
import android.text.TextUtils;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.widget.Toast;

import com.fondesa.recyclerviewdivider.RecyclerViewDivider;
import com.jakewharton.rxbinding2.view.RxView;
import com.kennyc.bottomsheet.BottomSheet;
import com.kennyc.bottomsheet.BottomSheetListener;
import com.kye.base.DebounceObservableTransformer;
import com.kye.base.Logger;
import com.kye.datetimepicker.DateTimePicker;
import com.kye.express.R;
import com.kye.express.business.base.BaseAppCompatActivity;
import com.kye.express.business.base.BaseToolbarActivity;
import com.kye.express.business.online_pay.detail.OnlinePayDetailActivity;
import com.kye.express.business.online_pay.history.OnlinePayHistoryActivity;
import com.kye.express.business.scanner.ScannerActivity;
import com.kye.express.databinding.ActivityOnlinePayBinding;
import com.kye.express.utils.DateTimeUtils;
import com.kye.express.utils.ScreenUtils;
import com.kye.express.utils.pay.OnPayStatusListener;
import com.kye.express.utils.pay.OnlinePayUtils;
import com.kye.express.view.KyeProgressDialog;
import com.kye.express.view.ToastManager;
import com.kye.model.UserSession;
import com.kye.model.bean.event.EventFactory;
import com.kye.model.bean.online.GetPayResultResultBean;
import com.kye.model.bean.online.GetUnpaidFreightListResultBean;
import com.kye.model.bean.online.request.GetAliPayUrlParams;
import com.kye.model.bean.online.request.GetTargeNoByWechatParams;
import com.scwang.smartrefresh.layout.api.RefreshLayout;
import com.scwang.smartrefresh.layout.listener.OnRefreshLoadmoreListener;
import com.tencent.mm.opensdk.modelbase.BaseResp;

import org.greenrobot.eventbus.EventBus;
import org.greenrobot.eventbus.Subscribe;
import org.greenrobot.eventbus.ThreadMode;

import java.text.DecimalFormat;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;

import io.reactivex.functions.Consumer;
import me.drakeet.multitype.Items;
import me.drakeet.multitype.MultiTypeAdapter;

/**
 * @Author chen
 * @Date 18/1/19 上午11:47
 * @descript 在线支付首页
 */


public class OnlinePayActivity extends BaseToolbarActivity implements OnlinePayActivityContract.OnlinePayActivityView, OnlinePayItemViewBinder.OnCheckedListener {
    private static final int REQUEST_CODE_SCANNER = 1;
    private ActivityOnlinePayBinding mBinding;

    private Context mContext;
    private OnlinePayActivityContract.OnlinePayActivityViewPresenter mPresenter;

    protected MultiTypeAdapter mAdapter;
    protected Items mDatas = new Items();
    private Dialog mLoadingDialog;
    private String mCurrentOrderNo = "";

    public static void startActivity(Context context) {
        Intent intent = new Intent(context, OnlinePayActivity.class);
        context.startActivity(intent);
    }

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        mBinding = DataBindingUtil.setContentView(this, R.layout.activity_online_pay);
        mContext = this;
        mPresenter = new OnlinePayActivityContract.OnlinePayActivityViewPresenter(this);
        mPresenter.bind(this);
        setUpToolbar((Toolbar) findViewById(R.id.toolbar));
        setTitle(getString(R.string.online_pay_title));
        initView();
        initEvent();
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        if (mPresenter != null) {
            mPresenter.unbind();
        }
        if (EventBus.getDefault().isRegistered(this)) {
            EventBus.getDefault().unregister(this);
        }
    }

    private void initView() {
        mAdapter = new MultiTypeAdapter();
        mAdapter.register(GetUnpaidFreightListResultBean.DatasBean.class, new OnlinePayItemViewBinder(mContext, this));
        mBinding.recyclerview.setLayoutManager(new LinearLayoutManager(mContext));
        RecyclerViewDivider.with(mContext)
                .color(getResources().getColor(R.color.grey))
                .size(ScreenUtils.dp2px(mContext, 1))
                .hideLastDivider()
                .build()
                .addTo(mBinding.recyclerview);
        mBinding.recyclerview.setItemAnimator(new DefaultItemAnimator());
        mAdapter.setItems(mDatas);
        mBinding.recyclerview.setAdapter(mAdapter);
        mBinding.refreshLayout.setOnRefreshLoadmoreListener(new OnRefreshLoadmoreListener() {
            @Override
            public void onRefresh(RefreshLayout refreshlayout) {
                mPresenter.getUnpaidFerigetList(false, false, "");
            }

            @Override
            public void onLoadmore(RefreshLayout refreshlayout) {
                mPresenter.getUnpaidFerigetList(false, true, "");
            }

        });
        mPresenter.getUnpaidFerigetList(true, false, "");
    }

    private void initEvent() {
        RxView.clicks(mBinding.ibAdd)
                .compose(new DebounceObservableTransformer<>())
                .compose(this.bindToLifecycleDestroy())
                .subscribe(new Consumer<Object>() {
                    @Override
                    public void accept(Object o) throws Exception {
                        String waybillNo = mBinding.edtWaybill.getText().toString().trim();
                        if (TextUtils.isEmpty(waybillNo)) {
                            ToastManager.show(mContext, R.string.invoice_online_waybill_is_null, Toast.LENGTH_SHORT);
                            return;
                        }
                        if (waybillNo.length() != 7 && waybillNo.length() != 11) {
                            ToastManager.show(mContext, R.string.online_pay_waybill_error, Toast.LENGTH_SHORT);
                            return;
                        }
                        mPresenter.findWaybillAmount(waybillNo);
                    }
                });
        RxView.clicks(mBinding.ivScan)
                .compose(new DebounceObservableTransformer<>())
                .compose(this.bindToLifecycleDestroy())
                .subscribe(new Consumer<Object>() {
                    @Override
                    public void accept(Object o) throws Exception {
                        startActivityForResult(new Intent(mContext, ScannerActivity.class), REQUEST_CODE_SCANNER);
                    }
                });
        RxView.clicks(mBinding.tvGenerate)
                .compose(new DebounceObservableTransformer<>())
                .compose(this.bindToLifecycleDestroy())
                .subscribe(new Consumer<Object>() {
                    @Override
                    public void accept(Object o) throws Exception {
                        double totalPrice = getTotalPrice();
                        if (totalPrice > 0) {
                            showSelectPayTypeDialog();
                        }
                    }
                });
        if (!EventBus.getDefault().isRegistered(this)) {
            EventBus.getDefault().register(this);
        }
    }

    @Override
    protected void onActivityResult(int requestCode, int resultCode, Intent data) {
        super.onActivityResult(requestCode, resultCode, data);
        if (requestCode == REQUEST_CODE_SCANNER && data != null) {
            String waybill = data.getStringExtra(ScannerActivity.KEY_SCANNER_RESULT);
            if (!TextUtils.isEmpty(waybill)) {
                mBinding.edtWaybill.setText(waybill);
            }
        }
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.menu_online_pay, menu);
        return true;
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        int id = item.getItemId();
        switch (id) {
            case R.id.menu_record:
                OnlinePayHistoryActivity.startActivity(this);
                break;
        }
        return super.onOptionsItemSelected(item);
    }

    @Override
    public void onComplete(boolean isLoadMore) {
        if (mLoadingDialog != null && mLoadingDialog.isShowing()) {
            mLoadingDialog.dismiss();
        }
        if (isLoadMore) {
            mBinding.refreshLayout.finishLoadmore();
        } else {
            mBinding.refreshLayout.finishRefresh();
        }

    }

    @Override
    public void onLoading() {
        try {
            if (mLoadingDialog == null) {
                mLoadingDialog = new KyeProgressDialog.Builder(mContext)
                        .build();
            }
            mLoadingDialog.show();
        } catch (Exception e) {

        }
    }

    @Override
    public void onLoaded(GetUnpaidFreightListResultBean resultDatas, boolean isLoadMore) {
        if (resultDatas != null) {
            List<GetUnpaidFreightListResultBean.DatasBean> datas2 = resultDatas.getDatas2();
            if (!isLoadMore) {
                mDatas.clear();
                if (datas2 != null) {
                    mDatas.addAll(datas2);
                }
                mAdapter.notifyDataSetChanged();
            } else {
                List<GetUnpaidFreightListResultBean.DatasBean> datas = (List<GetUnpaidFreightListResultBean.DatasBean>) mAdapter.getItems();
                if (datas != null) {
                    int start = datas.size();
                    if (datas2 != null) {
                        datas.addAll(datas2);
                    }
                    mAdapter.notifyDataSetChanged();
                }
            }
        }
        onDataChanged();
    }

    @Override
    public void onError(String msg, boolean isLoadMore) {
        ToastManager.show(mContext, msg, Toast.LENGTH_SHORT);
        if (isLoadMore) {
            mBinding.refreshLayout.finishLoadmore(false);
        } else {
            mBinding.refreshLayout.finishRefresh(false);
        }
        if (mLoadingDialog != null && mLoadingDialog.isShowing()) {
            mLoadingDialog.dismiss();
        }
        onDataChanged();
    }

    @Override
    public void onOtherError(String msg) {
        ToastManager.show(mContext, msg, Toast.LENGTH_SHORT);
        if (mLoadingDialog != null && mLoadingDialog.isShowing()) {
            mLoadingDialog.dismiss();
        }
    }

    private void onDataChanged() {
        if (mAdapter.getItems().size() <= 0) {
            mBinding.tvTips.setVisibility(View.VISIBLE);
            mBinding.cardview.setVisibility(View.GONE);
        } else {
            mBinding.tvTips.setVisibility(View.GONE);
            mBinding.cardview.setVisibility(View.VISIBLE);
        }
    }

    @Override
    public void onCompleteFindWaybillAmount() {
        if (mLoadingDialog != null && mLoadingDialog.isShowing()) {
            mLoadingDialog.dismiss();
        }
    }

    @Override
    public void onLoadedFindWaybillAmount(List<GetUnpaidFreightListResultBean.DatasBean> data) {
        if (data != null && data.get(0) != null && (!TextUtils.isEmpty(data.get(0).getWaybill()))) {
            boolean exist = false;
            List<GetUnpaidFreightListResultBean.DatasBean> datas = (List<GetUnpaidFreightListResultBean.DatasBean>) mAdapter.getItems();
            if (datas != null) {
                for (GetUnpaidFreightListResultBean.DatasBean item : datas) {
                    if (data.get(0).getWaybill().equals(item.getWaybill())) {
                        exist = true;
                        break;
                    }
                }
            }

            if (exist) {
                ToastManager.show(mContext, R.string.invoice_online_waybill_exist, Toast.LENGTH_SHORT);
            } else {
                ToastManager.show(mContext, R.string.common_query_successfully, Toast.LENGTH_SHORT);
                mDatas.addAll(0, data);
                mAdapter.notifyDataSetChanged();
            }
        }
    }

    @Override
    public void onErrorFindWaybillAmount(String msg) {
        ToastManager.show(mContext, msg, Toast.LENGTH_SHORT);
        if (mLoadingDialog != null && mLoadingDialog.isShowing()) {
            mLoadingDialog.dismiss();
        }
    }

    @Override
    public void onLoadedGetPayResult(GetPayResultResultBean data) {
        if (data != null) {
            if (data.isIsPay()) {
                OnlinePayDetailActivity.startActivity(mContext, mCurrentOrderNo, true);
            } else {
                ToastManager.show(mContext, R.string.online_pay_pay_failed, Toast.LENGTH_SHORT);
            }
        }
    }

    @Override
    public void onCheckStatusChanged() {
        double totalPrice = getTotalPrice();
        mBinding.tvTotalPrice.setText("￥" + totalPrice);
        if (totalPrice > 0) {
            mBinding.rlPrice.setBackgroundResource(R.drawable.common_shape_bg_green);
        } else {
            mBinding.rlPrice.setBackgroundResource(R.drawable.common_shape_bg_gray);
        }
    }

    private double getTotalPrice() {
        double totalPrice = 0;
        List<GetUnpaidFreightListResultBean.DatasBean> datas = (List<GetUnpaidFreightListResultBean.DatasBean>) mAdapter.getItems();
        if (datas != null) {
            for (GetUnpaidFreightListResultBean.DatasBean item : datas) {
                if (item.isChecked()) {
                    totalPrice += item.getAdvancePayment();
                }
            }
        }
        return totalPrice;
    }

    private List<GetUnpaidFreightListResultBean.DatasBean> getSelectedWaybillList() {
        List<GetUnpaidFreightListResultBean.DatasBean> selectList = new ArrayList<>();
        List<GetUnpaidFreightListResultBean.DatasBean> datas = (List<GetUnpaidFreightListResultBean.DatasBean>) mAdapter.getItems();
        if (datas != null) {
            for (GetUnpaidFreightListResultBean.DatasBean item : datas) {
                if (item.isChecked()) {
                    selectList.add(item);
                }
            }
        }
        return selectList;
    }

    private void showSelectPayTypeDialog() {

        new BottomSheet.Builder(this)
                .setSheet(R.menu.menu_bottomsheet_select_pay_type)
                .setTitle(R.string.common_pay_select_pay_type)
                .setListener(new BottomSheetListener() {
                    @Override
                    public void onSheetShown(@NonNull BottomSheet bottomSheet, @Nullable Object o) {

                    }

                    @Override
                    public void onSheetItemSelected(@NonNull BottomSheet bottomSheet, MenuItem menuItem, @Nullable Object o) {
                        mCurrentOrderNo = "";
                        if (menuItem.getItemId() == R.id.wechat) {
                            payByWechat();
                        } else {
                            payByAli();
                        }
                    }

                    @Override
                    public void onSheetDismissed(@NonNull BottomSheet bottomSheet, @Nullable Object o, int i) {

                    }
                })
                .show();

    }

    private void payByWechat() {
        List<GetUnpaidFreightListResultBean.DatasBean> waybillBeans = getSelectedWaybillList();
        if (waybillBeans != null && waybillBeans.size() > 0) {
            ArrayList<GetTargeNoByWechatParams.Data> dataArrayList = new ArrayList<>();
            StringBuilder sb = new StringBuilder();
            for (int i = 0; i < waybillBeans.size(); i++) {
                if (i == 0) {
                    sb.append(waybillBeans.get(i).getWaybill());
                } else {
                    sb.append("," + waybillBeans.get(i).getWaybill());
                }

                GetTargeNoByWechatParams.Data data = new GetTargeNoByWechatParams.Data();
                data.setPrePayment(waybillBeans.get(i).getAdvancePayment() + "");
                data.setIntoMonths("");
                data.setType("散客");
                data.setYdno(waybillBeans.get(i).getWaybill());
                data.setSendingTime(waybillBeans.get(i).getSendTime());
                dataArrayList.add(data);
            }
            if (UserSession.getInstance().getUser() != null) {
                DecimalFormat df = new DecimalFormat("######0"); //四色五入转换成整数
                String totalPrice = df.format(getTotalPrice() * 100);
                OnlinePayUtils.getInstance().onlinePayByWechat(this, sb.toString(), totalPrice, UserSession.getInstance().getUser(), dataArrayList, new OnPayStatusListener() {
                    @Override
                    public void onPaySuccess(Map<String, String> response) {
                        Logger.d("onPaySuccess");
                        String out_trade_no = response.get("out_trade_no");
                        mCurrentOrderNo = out_trade_no;
                    }

                    @Override
                    public void onPayFail(Map<String, String> errMap, String error) {
                        if (!TextUtils.isEmpty(error)) {
                            ToastManager.show(mContext, error, Toast.LENGTH_SHORT);
                        }
                    }
                });
            }
        }

    }

    private void payByAli() {
        List<GetUnpaidFreightListResultBean.DatasBean> waybillBeans = getSelectedWaybillList();
        if (waybillBeans != null && waybillBeans.size() > 0) {
            ArrayList<GetAliPayUrlParams.Data> dataArrayList = new ArrayList<>();
            StringBuilder sb = new StringBuilder();
            for (int i = 0; i < waybillBeans.size(); i++) {
                if (i == 0) {
                    sb.append(waybillBeans.get(i).getWaybill());
                } else {
                    sb.append("," + waybillBeans.get(i).getWaybill());
                }

                GetAliPayUrlParams.Data data = new GetAliPayUrlParams.Data();
                data.setCw_523(DateTimeUtils.getCurrentDate());
                data.setMoney(waybillBeans.get(i).getAdvancePayment() + "");
                data.setType("散客");
                data.setPaymentYdNo(waybillBeans.get(i).getWaybill());
                data.setSendTime(waybillBeans.get(i).getSendTime());
                dataArrayList.add(data);
            }
            if (UserSession.getInstance().getUser() != null) {
                OnlinePayUtils.getInstance().onlinePayByAli(this, sb.toString(), getTotalPrice() + "", UserSession.getInstance().getUser(), dataArrayList, new OnPayStatusListener() {
                    @Override
                    public void onPaySuccess(Map<String, String> response) {
                        Logger.d("onPaySuccess");
                        String msg = response.get("msg");
                        String out_trade_no = response.get("out_trade_no");
                        mCurrentOrderNo = out_trade_no;
                        getPayResult();
                    }

                    @Override
                    public void onPayFail(Map<String, String> errMap, String error) {
                        Logger.d("onPayFail:" + error);
                        if (errMap != null) {
                            String msg = errMap.get("msg");
                            ToastManager.show(mContext, msg, Toast.LENGTH_SHORT);
                        } else {
                            ToastManager.show(mContext, error, Toast.LENGTH_SHORT);
                        }
                    }
                });
            }
        }
    }

    @Subscribe(threadMode = ThreadMode.MAIN)
    public void onWechatPayCallBack(EventFactory.OnWechatPayEvent onWechatPayEvent) {
        if (onWechatPayEvent != null) {
            int code = onWechatPayEvent.code;
            if (BaseResp.ErrCode.ERR_OK == code) {
                getPayResult();
            } else {
                ToastManager.show(mContext, onWechatPayEvent.msg, Toast.LENGTH_SHORT);
            }
        }
    }

    /**
     * 向服务器获取支付结果
     */
    private void getPayResult() {
        if (!TextUtils.isEmpty(mCurrentOrderNo)) {
            mPresenter.findPayResult(mCurrentOrderNo);
        } else {
            ToastManager.show(mContext, R.string.online_pay_get_orderno_failed, Toast.LENGTH_SHORT);
        }
    }
}
